//
//  ViewController.m
//  FRP_OC
//
//  Created by DeLong Yang on 2017/8/4.
//  Copyright © 2017年 DeLongYang. All rights reserved.
/*
    地址：http://www.cocoachina.com/ios/20150123/10994.html
    主要用于演示 函数式编程 和 响应式编程 OC 版本
 */

#import "ViewController.h"
#import <ReactiveObjC/ReactiveObjC.h>
#import "RWDummySignService.h"  //
#import "DLViewController.h"    //
#import "DLCircleListViewController.h"   //
/*
 */


@interface ViewController ()

@property (weak, nonatomic) IBOutlet UITextField *userNameTextField;

@property (weak, nonatomic) IBOutlet UITextField *userPassWorldTextField;

@property (weak, nonatomic) IBOutlet UIButton *signInBtn;

// signInService
@property (strong,nonatomic) RWDummySignService *signInService;


@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];
    // Do any additional setup after loading the view, typically from a nib.
    
//    [self simpleTestTwo];
//    [self signalOfTestTwo];
//    [self signalTestThree];
//    [self signalTestFour];
//    [self signalTestFive];
//    [self combineSignal];
    
//    [self signalTestSeven];
    
    
//    [self signalTestNine];
    
//    [self signalTestTen];
//    [self signalTestEleven];
}


- (void)didReceiveMemoryWarning {
    [super didReceiveMemoryWarning];
    // Dispose of any resources that can be recreated.
}

// simple test  one
- (void)simpleTestOne
{
    [self.userNameTextField.rac_textSignal subscribeNext:^(id x){
        NSLog(@"%@", x);
    }];

}

// 过滤相应的 某些信号源 ›
- (void)simpleTestTwo
{
    [[self.userNameTextField.rac_textSignal filter:^BOOL(NSString * _Nullable value) {
        NSString *text =  value;
        return text.length > 3;
    }]
    subscribeNext:^(NSString * _Nullable x) {
        NSLog(@"%@", x);
    }];
}


// 下面这个 是 simpleTestTwo 的信号展示  信号 是关键所在
- (void)signalOfTestTwo
{
    RACSignal *userNameSourceSignal = self.userNameTextField.rac_textSignal;
    RACSignal *filterUserNameSignal = [userNameSourceSignal filter:^BOOL(id  _Nullable value) {
        NSString *text = value;
        return  text.length > 3;
    }];
    
    [filterUserNameSignal subscribeNext:^(id  _Nullable x) {
        NSLog(@"%@",x);
    }];
}

//  通过map 改变了 值的类型
/*
   新加的map操作通过block改变了事件的数据。map从上一个next事件接收数据，通过执行block把返回值传给下一个next事件。在上面的代码中，map以NSString为输入，取字符串的长度，返回一个NSNumber。
 */
- (void)signalTestThree
{
   [[[self.userNameTextField.rac_textSignal map:^id _Nullable(NSString * _Nullable value) {
       return  @(value.length);
   }]
    filter:^BOOL(NSNumber * value) {
        return [value integerValue] > 3;
    }]
    subscribeNext:^(id  _Nullable x) {
        NSLog(@"%@", x);
    }];
}

#pragma mark ---- 根据 输入的文字 改变textField 的backgroundColor
//
- (void)signalTestFour
{
    RACSignal *validUserNameSignal = [self.userNameTextField.rac_textSignal map:^id _Nullable(NSString * _Nullable value) {
        return @([self isValidUserName:value]);
    }];
    
    RACSignal *validPasswordSignal = [self.userPassWorldTextField.rac_textSignal map:^id _Nullable(NSString * _Nullable value) {
        return @([self isValidPassword:value]);
    }];
    
    //
    [[validUserNameSignal map:^id _Nullable(NSNumber *value) {
        return [value boolValue] ? [UIColor yellowColor]:[UIColor clearColor];
    }]
    subscribeNext:^(UIColor *x) {
        self.userNameTextField.backgroundColor = x;
    }];
    
    
    [[validPasswordSignal map:^id _Nullable(NSNumber *value) {
        return [value boolValue] ? [UIColor blueColor]:[UIColor clearColor];
    }]
    subscribeNext:^(id  _Nullable x) {
        UIColor *color = x;
        self.userPassWorldTextField.backgroundColor = color;
    }];
}

- (BOOL)isValidUserName:(NSString *)userName
{
    return [userName isEqualToString:@"abc"];
}

- (BOOL)isValidPassword:(NSString *)passWord
{
    return [passWord isEqualToString:@"123"];
}


#pragma mark --- 对方法四的改进。使用 RAC。宏定义
//
- (void)signalTestFive
{
    RACSignal *validUserNameSignal = [self.userNameTextField.rac_textSignal map:^id _Nullable(NSString * _Nullable value) {
        return @([self isValidUserName:value]);
    }];
    
    RACSignal *validPasswordSignal = [self.userPassWorldTextField.rac_textSignal map:^id _Nullable(NSString * _Nullable value) {
        return @([self isValidPassword:value]);
    }];
    
    RAC(self.userNameTextField,backgroundColor) = [validUserNameSignal map:^id _Nullable(NSNumber *value) {
        return [value boolValue] ? [UIColor redColor]:[UIColor clearColor];
    }];
    
    RAC(self.userPassWorldTextField,backgroundColor) = [validPasswordSignal map:^id _Nullable(NSNumber * value) {
       return [value boolValue] ? [UIColor yellowColor]:[UIColor clearColor];
    }];
}

#pragma mark ----   信号的 聚合
// we combine the two signal
- (void)combineSignal
{
    RACSignal *validUserNameSignal = [self.userNameTextField.rac_textSignal map:^id _Nullable(NSString * _Nullable value) {
        return @([self isValidUserName:value]);
    }];
    
    RACSignal *validPasswordSignal = [self.userPassWorldTextField.rac_textSignal map:^id _Nullable(NSString * _Nullable value) {
        return @([self isValidPassword:value]);
    }];
    //
    
    RAC(self.userNameTextField,backgroundColor) = [validUserNameSignal map:^id _Nullable(NSNumber *value) {
        return [value boolValue] ? [UIColor redColor]:[UIColor clearColor];
    }];
    
    RAC(self.userPassWorldTextField,backgroundColor) = [validPasswordSignal map:^id _Nullable(NSNumber * value) {
        return [value boolValue] ? [UIColor yellowColor]:[UIColor clearColor];
    }];

    //
    RACSignal *signUpActiveSignal = [RACSignal combineLatest:@[validUserNameSignal,validPasswordSignal] reduce:^id (NSNumber*usernameValid, NSNumber *passwordValid){
        return @(usernameValid.boolValue && passwordValid.boolValue);
    }];
    
    // block 里的参数是可以自己改 的
    [signUpActiveSignal subscribeNext:^(NSNumber *x) {
        self.signInBtn.enabled = [x boolValue];
    }];
    
}

#pragma mark ----  UIButton  Reactive
//
- (void)signalTestSeven
{
    [[self.signInBtn
     rac_signalForControlEvents:UIControlEventTouchUpInside]
    subscribeNext:^(__kindof UIControl * _Nullable x) {
        NSLog(@"button clicked ");
    }];
}

#pragma mark ----  创建信号

- (RACSignal *)signInSignal
{
    return  [RACSignal createSignal:^RACDisposable * _Nullable(id<RACSubscriber>  _Nonnull subscriber) {
        [self.signInService signInWithUserName:self.userNameTextField.text password:self.userPassWorldTextField.text complete:^(BOOL success) {
            [subscriber sendNext:@(success)];
            [subscriber sendCompleted];
        }];
        return nil;
    }];
}

- (RWDummySignService *)signInService
{
    if (!_signInService) {
        _signInService = [[RWDummySignService alloc]init];
    }
    return _signInService;
}

#pragma mark ---- use created signal 
- (void)signalTestNine
{
    [[[self.signInBtn rac_signalForControlEvents:UIControlEventTouchUpInside]
     map:^id _Nullable(__kindof UIControl * _Nullable value) {
         return  [self signInService];
     }]
    subscribeNext:^(id  _Nullable x) {
        NSLog(@"sign in result :%@",x);
    }];
}


//
- (void)signalTestTen
{
    //
    [[[self.signInBtn
       rac_signalForControlEvents:UIControlEventTouchUpInside]
      flattenMap:^id(id x){
          return[self signInSignal];
      }]
     subscribeNext:^(id x){
         NSLog(@"Sign in result: %@", x);
     }];
}

// xin
- (void)signalTestEleven
{
    [[[self.signInBtn rac_signalForControlEvents:UIControlEventTouchUpInside]
     flattenMap:^__kindof RACSignal * _Nullable(__kindof UIControl * _Nullable value) {
        return  [self signInSignal];
    }]
    subscribeNext:^(NSNumber *value) {
        BOOL success = [value boolValue];
        if (success) {
//            [self performSegueWithIdentifier:@"signInSuccess" sender:self];
            UIViewController *vc = [[UIViewController alloc]init];
            [self.navigationController pushViewController:vc animated:NO];
        }else{
            NSLog(@"username  or  pass error ");
        }
    }];
}

#pragma mark ----  Optimise Experiece
// we need to optimise use experience
// 我们认为。
- (void)optimiseExperience
{
    [[[[self.signInBtn
        rac_signalForControlEvents:UIControlEventTouchUpInside]
       doNext:^(id x){
           self.signInBtn.enabled =NO;
//           self.signInFailureText.hidden =YES;
       }]
      flattenMap:^id(id x){
          return[self signInSignal];
      }]
     subscribeNext:^(NSNumber*signedIn){
         self.signInBtn.enabled =YES;
         BOOL success =[signedIn boolValue];
//         self.signInFailureText.hidden = success;
         if(success){
             [self performSegueWithIdentifier:@"signInSuccess" sender:self];
         }
     }];
}

#pragma mark ----  点击 table
//
- (IBAction)dlTableClick:(id)sender
{
    //
    DLViewController *dlVC = [[DLViewController alloc] initWithNibName:@"DLViewController" bundle:nil];
    [self.navigationController pushViewController:dlVC animated:YES];
    
}


#pragma mark ---- 点击  社团列表界面
- (IBAction)clickDLCircleListVC:(id)sender
{
    DLCircleListViewController *circleVC = [[DLCircleListViewController alloc] init];
    [self.navigationController pushViewController:circleVC animated:YES];
}




@end






























































